#include "ShoppingCart.h"

// 清空购物车
void ShoppingCart::clear()
{
    itemMap.clear();
    std::cout << "购物车已清空。\n";
}

// 检查商品是否已在购物车中
bool ShoppingCart::isInCart(const std::string &productId) const
{
    return itemMap.count(productId) > 0; // map::count 比 find 然后比较更简洁
}

// 查看购物车内容
// void ShoppingCart::viewCart() const
// { // viewCart 不应修改成员，故标记为 const
//     if (isEmpty())
//     {
//         std::cout << "购物车是空的。\n\n";
//         return;
//     }
//     std::cout << "--- 购物车内容 ---\n";
//     double cartTotalPrice = 0.0; // 使用 double 计算总价
//     int itemNumber = 1;

//     std::cout << std::left << std::setw(5) << "序号"
//               << std::setw(15) << "商品ID"
//               << std::setw(30) << "商品名称"
//               << std::setw(10) << "单价"
//               << std::setw(10) << "数量"
//               << std::setw(10) << "小计" << std::endl;
//     std::cout << "---------------------------------------------------------------------------\n";

//     for (const auto &pair : itemMap)
//     {
//         const CartItem &cartItem = pair.second;
//         if (cartItem.product && cartItem.quantity > 0)
//         { // 确保 product 有效且数量大于0
//             double itemPrice = cartItem.product->getPrice();
//             double itemSubtotal = itemPrice * cartItem.quantity;
//             cartTotalPrice += itemSubtotal;

//             std::cout << std::left << std::setw(5) << itemNumber++
//                       << std::setw(15) << cartItem.product->getId()
//                       << std::setw(30) << cartItem.product->getName()
//                       << std::fixed << std::setprecision(2) << std::setw(10) << itemPrice
//                       << std::setw(10) << cartItem.quantity
//                       << std::fixed << std::setprecision(2) << std::setw(10) << itemSubtotal
//                       << std::endl;
//         }
//     }
//     std::cout << "---------------------------------------------------------------------------\n";
//     std::cout << "购物车总价: ¥" << std::fixed << std::setprecision(2) << cartTotalPrice << "\n\n";
// }

// 添加商品到购物车
void ShoppingCart::addItem(Product &originalProduct, int qty)
{
    if (qty <= 0)
    {
        std::cout << "添加失败：数量必须大于0。\n";
        return;
    }

    if (originalProduct.getAvailableQuantity() < qty)
    {
        std::cout << "添加失败：商品 [" << originalProduct.getName() << "] 库存不足。"
                  << " 当前可用库存: " << originalProduct.getAvailableQuantity() << "\n";
        return;
    }

    const std::string &productId = originalProduct.getId();
    if (isInCart(productId))
    {
        // 商品已在购物车中，检查增加数量后是否超出库存
        int currentQtyInCart = itemMap.at(productId).quantity;
        if (originalProduct.getAvailableQuantity() < (currentQtyInCart + qty - currentQtyInCart /*实际上就是qty*/))
        { // 更准确的库存检查逻辑
            std::cout << "添加失败：商品 [" << originalProduct.getName() << "] 库存不足以增加指定数量。"
                      << " 当前购物车已有 " << currentQtyInCart << ", 再增加 " << qty
                      << " 将超过可用库存 " << originalProduct.getAvailableQuantity() << "\n";
            return;
        }
        itemMap.at(productId).quantity += qty;
        std::cout << "商品 [" << originalProduct.getName() << "] 已在购物车中，数量已更新为 "
                  << itemMap.at(productId).quantity << "。\n";
    }
    else
    {
        // 商品不在购物车中，克隆原始商品并添加
        std::unique_ptr<Product> productClone = originalProduct.clone(); // 使用 clone
        if (!productClone)
        {
            std::cerr << "错误：克隆商品 [" << originalProduct.getName() << "] 失败。\n";
            return;
        }
        // itemMap[productId] = CartItem(std::move(productClone), qty); // 使用 CartItem 的构造函数和移动赋值
        // 或者更高效地使用 emplace
        itemMap.emplace(productId, CartItem(std::move(productClone), qty));

        std::cout << "已添加商品 [" << originalProduct.getName() << "] 到购物车，数量为 " << qty << "。\n";
    }
}

// 从购物车移除商品
bool ShoppingCart::removeItem(const std::string &productId, int qtyToRemove)
{
    if (qtyToRemove < 0)
    {
        std::cout << "移除失败：数量必须大于等于0。\n";
        return false;
    }
    if (!isInCart(productId))
    {
        std::cout << "移除失败：商品ID [" << productId << "] 不在购物车中。\n";
        return false;
    }

    CartItem &itemInCart = itemMap.at(productId); // 获取引用以便修改

    if (itemInCart.quantity <= qtyToRemove || qtyToRemove == 0)
    {
        itemMap.erase(productId); // 如果移除数量大于等于当前数量，则直接删除该商品项
        std::cout << "商品 [" << (itemInCart.product ? itemInCart.product->getName() : productId)
                  << "] 已从购物车中完全移除。\n";
    }
    else
    {
        itemInCart.quantity -= qtyToRemove;
        std::cout << "商品 [" << (itemInCart.product ? itemInCart.product->getName() : productId)
                  << "] 的数量已减少 " << qtyToRemove << "，剩余 " << itemInCart.quantity << "。\n";
    }
    return true;
}

// 更新购物车中商品的数量
bool ShoppingCart::updateItemQuantity(const std::string &productId, int newQty, ProductController *productCtrl)
{
    if (!isInCart(productId))
    {
        std::cout << "更新失败：商品ID [" << productId << "] 不在购物车中。\n";
        return false;
    }

    CartItem &itemInCart = itemMap.at(productId);
    std::string productName = itemInCart.product ? itemInCart.product->getName() : productId;

    if (newQty <= 0)
    {
        itemMap.erase(productId);
        std::cout << "商品 [" << productName << "] 数量更新为0或负数，已从购物车移除。\n";
        return true;
    }

    // 如果是增加数量，需要检查原始库存
    // 注意：这里的 itemInCart.product 是克隆副本，其 getAvailableQuantity() 是快照。
    // 我们需要原始商品的库存信息。
    if (newQty > itemInCart.quantity)
    {
        int additionalQty = newQty - itemInCart.quantity;
        if (productCtrl)
        {
            Product *originalProduct = productCtrl->findProductById(productId);
            if (!originalProduct)
            {
                std::cerr << "错误：更新商品 [" << productName << "] 数量时，无法在商品库中找到原始商品信息。\n";
                return false;
            }
            if (originalProduct->getAvailableQuantity() < additionalQty)
            {
                std::cout << "更新失败：商品 [" << productName << "] 库存不足以增加到 " << newQty
                          << "。当前可用库存: " << originalProduct->getAvailableQuantity() << "\n";
                return false;
            }
        }
        else
        {
            // 如果没有 ProductController，我们无法安全地检查增加数量时的库存
            // 可以选择允许，或提示需要 ProductController
            std::cout << "警告：正在增加商品 [" << productName << "] 数量，但未提供库存检查机制。"
                      << " 请确保库存充足。\n";
            // 或者直接不允许增加，并返回 false
            // std::cerr << "错误: 增加商品数量需要 ProductController 进行库存校验。\n";
            // return false;
        }
    }

    itemInCart.quantity = newQty;
    std::cout << "商品 [" << productName << "] 数量已更新为 " << newQty << "。\n";
    return true;
}

// 计算购物车中所有商品的总价
double ShoppingCart::calculateTotalPrice() const
{
    double totalPrice = 0.0;
    for (const auto &pair : itemMap)
    {
        const CartItem &cartItem = pair.second;
        if (cartItem.product && cartItem.quantity > 0)
        {
            totalPrice += cartItem.product->getPrice() * cartItem.quantity;
        }
    }
    return totalPrice;
}

// 获取购物车中不同种类商品的数量
size_t ShoppingCart::getDistinctItemCount() const
{
    return itemMap.size();
}

// 获取购物车中所有商品的总件数
int ShoppingCart::getTotalItemQuantity() const
{
    int totalQuantity = 0;
    for (const auto &pair : itemMap)
    {
        totalQuantity += pair.second.quantity;
    }
    return totalQuantity;
}

// 获取购物车中的所有商品项 (例如用于创建订单，返回副本)
std::vector<CartItem> ShoppingCart::getItems() const
{
    std::vector<CartItem> itemsVec;
    itemsVec.reserve(itemMap.size()); // 预分配空间
    for (const auto &pair : itemMap)
    {
        if (pair.second.product && pair.second.quantity > 0)
        {
            itemsVec.push_back(pair.second); // CartItem 的拷贝构造函数会被调用
        }
    }
    return itemsVec;
}

// ShoppingCart.cpp 或你的实现文件

// 【新增】购物车序列化为 JSON
json ShoppingCart::toJson() const
{
    json j_cart = json::array();
    for (const auto &pair : itemMap)
    {
        const auto &item = pair.second;
        if (item.product && item.quantity > 0)
        {
            json j_item;
            j_item["productId"] = item.product->getId();
            j_item["quantity"] = item.quantity;
            j_cart.push_back(j_item);
        }
    }
    return j_cart;
}

// 【新增】从 JSON 加载购物车
void ShoppingCart::loadFromJson(const json &j_cart, ProductController &productCtrl)
{
    this->itemMap.clear();
    if (!j_cart.is_array())
        return;

    for (const auto &j_item : j_cart)
    {
        if (j_item.is_object() && j_item.contains("productId") && j_item.contains("quantity"))
        {
            std::string pid = j_item.at("productId").get<std::string>();
            int qty = j_item.at("quantity").get<int>();

            Product *p = productCtrl.findProductById(pid);
            if (p)
            {
                // 直接添加，不进行库存检查，因为这是恢复之前的状态
                this->addItem(*p, qty);
            }
            else
            {
                std::cerr << "警告：加载购物车时，未找到商品ID " << pid << "，该项已忽略。\n";
            }
        }
    }
}